home *** CD-ROM | disk | FTP | other *** search
/ Magazyn Exec 1 / CD_Magazyn_EXEC_nr_1.iso / eXec / Analiza i kompresja mowy / lpcCodec_v4.m < prev    next >
Text File  |  2000-01-11  |  6KB  |  235 lines

  1. function []=lpccodec_v4(plik_in,plik_out)
  2. % Koder LPC, Kwant 1999
  3. %
  4. % Sposób u¿ycia:
  5. %     lpccodec('plik_wejœciowy.wav', 'plik_wyjœciowy.wav');
  6. %
  7. %    Wymagana wersja matlab: 5.x
  8. %
  9. % lpcCodec.m
  10.  
  11.  
  12.  
  13.  
  14. % ====================  koder  =====================      
  15.  
  16. % czytanie pliku  wejœciowego
  17.     [x]= wavread( plik_in );
  18.     Fs= 8000;
  19.  
  20. % obliczanie d³ugoœci pliku
  21.     eof= length(x);
  22.  
  23. % lpc nieprawid³owo dzia³a na zerowych próbkach wiêc niedopuszczam do tego
  24.     for l=1:eof
  25.       if( x(l)==0 )
  26.         x(l)=eps;
  27.         end
  28.     end
  29.  
  30. % Filtrowanie sygnalu wejsciowego filtrem BP 10-900Hz
  31. % ograniczenie pasma dla sygna³u z którego bêdzie obliczany pitch
  32.     Impulse= fir1( 128, [50/(Fs/2) 900/(Fs/2)], 'high' );
  33.     PitchX_orig= filter(Impulse, 1, [x; zeros(128,1)] );
  34.     PitchX= PitchX_orig( 65:eof+64 );
  35.  
  36. % preemfaza uwypuklenie wysokich czêstotliowœci
  37.     x(2:eof)=x(2:eof)-0.9375*x(1:eof-1);
  38.  
  39. % potrzebne do autokorelacji
  40.     n=1:240;                              
  41.     index=1;
  42.     maximum=zeros(1,240);
  43.  
  44. %    wstêpne przeliczone wartoœci
  45. %    okno Hamminga
  46.     h= Hamming( 240 );
  47.  
  48. %    g³ówna pêtla encodera
  49.     for l=1:180:eof-240
  50.  
  51.     % 'we' sygna³ bie¿¹cej ramki
  52.       we=x(l:l+239).*h;
  53.    
  54.     %    kombinacje w celu poprawnego obliczenia wartoœci pitch, clipping
  55.         PitchXnoWin=[PitchX(l:l+239)' zeros(1,240)];  
  56.         Cl=0.7*min( max(PitchXnoWin(1:80)), max(PitchXnoWin(80:240)) );
  57.  
  58.     % clipping sygna³u (aby uwypukliæ czêstotliwoœæ g³ówn¹)
  59.         for k=1:480
  60.         if PitchXnoWin(k)>= Cl
  61.           clipper(k)=PitchXnoWin(k)-Cl;
  62.             elseif PitchXnoWin(k)<=-Cl
  63.                  clipper(k)=PitchXnoWin(k)+Cl;
  64.             else
  65.                 clipper(k)=0;
  66.             end
  67.         end
  68.    
  69.     %    Autokorelacja  
  70.    auto=zeros(1,240);
  71.    for K=0:239
  72.       auto(K+1)=sum( clipper(n).*clipper(n+K) );
  73.    end
  74.    
  75.     %    Maksima autokorelacji
  76.    maximum_1=maximum;     %maksima z poprzedniej iteracji
  77.    maximum(1)=0;
  78.    for K=2:239
  79.       if auto(K-1)<auto(K) & auto(K)>auto(K+1)
  80.          if auto(K)>0
  81.             maximum(K)=auto(K);
  82.          else
  83.             maximum(K)=0;
  84.          end
  85.       elseif auto(K-1)<auto(K) & auto(K)==auto(K+1) %maksimum p³askie
  86.          z=K+1;
  87.          while auto(K)==auto(z) & z<239
  88.             z=z+1;
  89.          end
  90.          
  91.          for y=K:z
  92.             if auto(K)>auto(z)
  93.                maximum(y)=auto(K);
  94.             else
  95.                maximum(y)=0;
  96.             end
  97.          end
  98.          K=z;
  99.       else
  100.          maximum(K)=0;
  101.       end
  102.         end
  103.    
  104.         [max1 imax1]=max(maximum_1);
  105.         [max0 imax0]=max(maximum);
  106.   
  107.     %    Okreœlanie czy g³oska jest dŸwiêczna czy bezdŸwiêczna
  108.     %    Jest to krytyczna faza kodera, od prawid³owej decyzji voiced/unvoiced zale¿y w znacznym stopniu jakoœæ generowanego dŸwiêku 
  109.         if imax1+imax1*0.2>imax0 & imax1-imax1*0.2<imax0
  110.             if max0>0.3*auto(1)
  111.                 Pitch=imax0;
  112.       else
  113.          Pitch=0;
  114.       end
  115.         else
  116.       Pitch=0;
  117.         end
  118.    
  119. %    To samo co wy¿ej tylko w mniej wyrafinowany sposób.
  120. %
  121. %    if max0 > 0.3*auto(1)
  122. %        Pitch= imax0;
  123. %    else
  124. %        Pitch= 0;
  125. %    end
  126.  
  127.     %    LPC wykorzystujê funkcjê LPC z Matlaba
  128.         [A G]=lpc(we,10);
  129.     
  130.     %    Sk³adanie danych wyjœciowych 
  131.         Coeff(index,1:11)=A;        % parametry LPC
  132.         Coeff(index,12)=G;            %    wzmocnienie
  133.         Coeff(index,13)=Pitch;    % Pitch (jeœli Pitch=0 to g³oska jest bezdŸwiêczna), w przeciwnym wypadku pitch jest odleg³oœci¹ pomiêdzy kolejnymi impulsami pobudzenia (w samplach Fs= 8000Hz)
  134.    
  135.     %
  136.         if index>=2 & Coeff(index,13)>0 & Coeff(index-1,13)==0
  137.             Coeff(index-1,13)=imax1;
  138.         end
  139.    
  140.     %    numer kolejnej ramki
  141.         index=index+1
  142.     end
  143.  
  144. %    likwidowanie pojedynczych szumow....
  145. %    Jeœli kolejne trzy ramki s¹: V, UV, V to œrodkow¹ ustaw jako Voiced
  146. %    Jeœli kolejne trzy ramki s¹: UV, V, UV to œrodkow¹ ustaw jako Unvoiced
  147.     for l=1:index-3
  148.         if Coeff(l,13)>0 & Coeff(l+1,13)==0 & Coeff(l+2,13)>0
  149.        Coeff(l+1,13)=round((Coeff(l,13)+Coeff(l+2,13))/2);
  150.     elseif Coeff(l,13)==0 & Coeff(l+1,13)>0 & Coeff(l+2,13)==0
  151.        Coeff(l+1,13)=0;
  152.     end
  153.  end
  154.  
  155. % ================= Koniec Kodera ==================
  156.  
  157.  
  158.  
  159.  
  160. %    Parametrami transferowymi jest tablica (macierz) Coeff(...,...) Opis wy¿ej.
  161. % modyfikuj¹c t¹ tablicê (patrz ni¿ej) mo¿na uzyskaæ ciekawe efekty!
  162.  
  163. % Tylko szept
  164. %    Coeff( :, 13 )= 0;
  165.  
  166. % Wszystko tym samym tonem (œrednim z ca³ej próbki)
  167. %    Coeff( :, 13 )= round( mean( Coeff(:,13) ).*( Coeff(:,13)~=0 ) );
  168.  
  169. %    Wszystko tym samym tonem, tylko ni¿ej
  170. %    Coeff( :, 13 )= round( mean( Coeff(:,13)*4 ).*( Coeff(:,13)~=0 ) );
  171.  
  172. % dwa razy ni¿sza czêstotliwoœæ podstawowa (Pitch = Pitch/2)
  173.     Coeff( :, 13 )= Coeff( :, 13 ).*2;
  174.  
  175. % dyskretne wartoœci Pitch
  176. %    Coeff( :, 13 )= round( Coeff(:, 13)./16 ).*16;
  177.  
  178. % Wszystkie g³oski tak samo g³oœno
  179. %    Coeff( :, 12 )= mean( Coeff(:, 12) );
  180.  
  181.  
  182.  
  183.  
  184. % ===================  Dekoder  ====================
  185.  
  186.     LastPitch=0;
  187.     excit=zeros(1,index*180);
  188.     count=1;
  189.     Coeff(1,:)=Coeff(2,:);           %przepisanie pierwszej wartosci Coeff bo jest nieprawidlowa
  190.  
  191. %    generowanie CA£EGO pobudzenia
  192.     for l=1:180:(index-1)*180
  193.         if Coeff(count,13)==0                          %unvoiced
  194.             r= randn( 1, 180 );
  195.             r= r/max( abs(r) );
  196.       excit(l:l+179)=(rand(1,180)*2-1);
  197.       LastPitch=0;
  198.         else                                           %voiced
  199.       for x= l+Coeff(count,13)-LastPitch:Coeff(count,13):l+179
  200.                 excit(x)= 1;
  201.       end
  202.       LastPitch=l+179-x;
  203.         end
  204.         count=count+1;
  205.     end   
  206.  
  207. % g³oœnoœæ:
  208.     sin2=sin((1:360)*pi/360).*sin((1:360)*pi/360);
  209.     for l=1:index-2
  210.       for x=1:180
  211.         excit(l*180+x-90)=excit(l*180+x-90) * (Coeff(l,12)*sin2(x+180)+Coeff(l+1,12)*sin2(x));
  212.         end
  213.     end
  214.  
  215. %    filtr LPC
  216.     Coeff(:,2:11)=- Coeff(:,2:11);
  217.  
  218.     for l=11:(index-1)*180 
  219.        excit(l)=sum(excit(l:-1:l-10).*Coeff( ceil(l/180) ,1:11));
  220.     end
  221.  
  222. %    deemfaza
  223.     excit(2:(index-1)*180)=excit(2:(index-1)*180)+0.9375*excit(1:(index-1)*180-1);
  224.  
  225. % normowanie sygna³u
  226.     excit( length(excit)-180*3: length(excit) )= 0;
  227.     excit( 1:180 )= 0;
  228.     max_output=max(excit);
  229.     min_output=-min(excit);
  230.     out=excit/max([min_output,max_output]);
  231.  
  232. % zapis do pliku
  233.     wavwrite(out,8000,16, plik_out );
  234.  
  235.